/**********************************************************************
* Filename: Jogador.java
* Created: 2012/04/30
* @author Fernando Brito e Abreu
**********************************************************************/
package org.bunny.businessLayer;

import java.util.Set;
import java.util.HashSet;

public class Jogador extends Participante{
	public static Set<Jogador> allInstances = new HashSet<Jogador>();
	
	private PosicaoJogador posicao;
	private Clube clube;
	
	/**********************************************************************
	* Default constructor
	**********************************************************************/
	public Jogador(){
		super();
		allInstances.add(this);
	}
	
	/**********************************************************************
	* Parameterized constructor
	* @param data_nascimento the data_nascimento to initialize (inherited)
	* @param nome the nome to initialize (inherited)
	* @param nacionalidade the nacionalidade to initialize (inherited)
	* @param posicao the posicao to initialize
	* @param clube the clube to initialize
	**********************************************************************/
	public Jogador(CalendarDate data_nascimento, String nome, Pais nacionalidade, PosicaoJogador posicao, Clube clube){
		super(data_nascimento, nome, nacionalidade);
		this.posicao = posicao;
		this.clube = clube;
		allInstances.add(this);
	}
	
	/**********************************************************************
	* Standard attribute getter
	* @return the posicao of the jogador
	**********************************************************************/
	public PosicaoJogador posicao(){
		return posicao;
	}
	
	/**********************************************************************
	* Standard attribute setter
	* @param posicao the posicao to set
	**********************************************************************/
	public void setPosicao(PosicaoJogador posicao){
		this.posicao = posicao;
	}
	
	/**********************************************************************
	* ONE2MANY getter for Jogador[*] <-> Clube[1]
	* @return the clube of the jogador
	**********************************************************************/
	public Clube clube(){
		return clube;
	}
	
	/**********************************************************************
	* ONE2MANY setter for Jogador[*] <-> Clube[1]
	* @param clube the clube to set
	**********************************************************************/
	public void setClube(Clube clube){
		this.clube = clube;
	}
	
	/**********************************************************************
	* MANY2MANY getter for Jogador[*] <-> Participacao[*]
	* @return the participacoes of the plantel
	**********************************************************************/
	public Set<Participacao> participacoes(){
		Set<Participacao> result = new HashSet<Participacao>();
		for (Participacao x : Participacao.allInstances){
			if (x.plantel().contains(this))
				result.add(x);
		}
		return result;
	}
	
	/**********************************************************************
	* MANY2MANY setter for Jogador[*] <-> Participacao[*]
	* @param participacoes the participacoes to set
	**********************************************************************/
	public void setParticipacoes(Set<Participacao> participacoes){
		for (Participacao x : participacoes){
			x.plantel().add(this);
	}
	}
	
	/**********************************************************************
	* MEMBER2ASSOCIATIVE getter for Jogador[11..*] <-> Membro[*]
	* @return the membro of the jogador
	**********************************************************************/
	public Set<Membro> membro(){
		Set<Membro> result = new HashSet<Membro>();
		for (Membro x : Membro.allInstances){
			if (x.jogador()  ==  this)
				result.add(x);
		}
		return result;
	}
	
	/**********************************************************************
	* MEMBER2ASSOCIATIVE setter for Jogador[11..*] <-> Membro[*]
	* @param membro the membro to set
	**********************************************************************/
	public void setMembro(Set<Membro> membro){
		for (Membro x : membro){
			x.setJogador(this);
		}
	}
	
	/**********************************************************************
	* MEMBER2MEMBER getter for Jogador[11..*] <-> Equipa[*]
	* @return the equipa of the jogador
	**********************************************************************/
	public Set<Equipa> equipa(){
		Set<Equipa> result = new HashSet<Equipa>();
		for (Membro x : Membro.allInstances){
			if (x.jogador()  ==  this)
				result.add(x.equipa());
		}
		return result;
	}
	
	/**********************************************************************
	* MEMBER2MEMBER setter for Jogador[11..*] <-> Equipa[*]
	* @param equipa the equipa to set
	**********************************************************************/
	public void setEquipa(Set<Equipa> equipa){
		for (Equipa t : equipa){
			for (Membro x: Membro.allInstances){
				if (x.jogador() == this)
					x.setEquipa(t);
			}
		}
	}
	
//	/**********************************************************************
//	* User-defined operation specified in SOIL/OCL
//	* @param nome the nome to set
//	* @param data_nascimento the data_nascimento to set
//	* @param posicao the posicao to set
//	* @param nacionalidade the nacionalidade to set
//	* @param clube the clube to set
//	**********************************************************************/
//	public void inicializa(String nome, CalendarDate data_nascimento, PosicaoJogador posicao, Pais nacionalidade, Clube clube){
//		//	TODO
//		this.nome = nome;
//		this.data_nascimento = data_nascimento;
//		this.posicao = posicao;
//		//	self.nome := nome;
//		//	 self.data_nascimento := data_nascimento;
//		//	 self.posicao := posicao;
//		//	 insert (nacionalidade,self) into Pais_Participante;
//		//	 insert (clube,self) into Clube_Jogador;
//	}
	
	//	PRE-CONDITIONS (TODO)
	/*
	pre JogadorArgumentosDefinidos
		((((nome.isDefined and data_nascimento.isDefined) and posicao.isDefined) and nacionalidade.isDefined) and clube.isDefined)
	
	*/
	
	//	POST-CONDITIONS (TODO)
	/*
	post JogadorInicializado
		((self.nome.isDefined and self.data_nascimento.isDefined) and self.posicao.isDefined)
	
	*/
	
	/**********************************************************************
	* User-defined operation specified in SOIL/OCL
	* @param c the c to set
	**********************************************************************/
	public void mudaClube(Clube c){
		this.clube = c;
		//	delete (self.clube,self) from Clube_Jogador;
		//	 insert (c,self) into Clube_Jogador;
	}
	
	//	PRE-CONDITIONS (TODO)
	/*
	pre ClubeEstaDefinido
		c.isDefined
	
	*/
	
	/* (non-Javadoc)
	* @see java.lang.Object#toString()
	*/
	@Override
	/**********************************************************************
	* Object serializer
	**********************************************************************/
	public String toString(){
		return "Jogador [posicao=" + posicao + ", clube=" + clube + "]\n";
	}
	
	//	-------------------------------------------------------------------------------
	//	INVARIANTS (TODO)
	/*
	inv JogadorSoJogaPorUmClube
		(self.clube->size = 1)
	
	*/
}
